package org.pps.gl.server.datastore;

import java.util.List;

import com.google.appengine.api.datastore.Entity;
import com.google.appengine.api.datastore.FetchOptions;
import com.google.appengine.api.datastore.Key;
import com.google.appengine.api.datastore.KeyFactory;
import com.google.appengine.api.datastore.Query;
import com.google.appengine.api.datastore.Query.FilterOperator;

public class Etude {

	public final static String nomEntity = "Etudes";
	
	/**
	 * Créer ou met a jour les études pour un User spécifique.
	 * 
	 * @param emailUser
	 *            : email de l'user concerné.
	 * @param periode
	 *            : Période de temps pour ces études
	 * @return
	 */
	public static Entity createEtude(Entity profil, String periode, String email_user) {

		Entity etude = new Entity(nomEntity);
		etude.setProperty("email_user", email_user);
		etude.setProperty("periode", periode);
		Util.persistEntity(etude);
		return etude;

	}

	/**
	 * Récupère toutes les études d'un profil.
	 * 
	 * @param profil
	 *            : profil de l'user
	 * @return: toutes les études du type user
	 */
	/*public static Iterable<Entity> getEtudesForProfil(Entity profil) {
		Key ancestorKey = profil.getKey();
		return Util.listChildren(nomEntity, ancestorKey);
	}*/
	public static Iterable<Entity> getEtudesForProfil(String emailUser) {
		Query query = new Query(nomEntity);
		query.addFilter("email_user", FilterOperator.EQUAL, emailUser);
		List<Entity> results = Util.getDatastoreServiceInstance()
				.prepare(query).asList(FetchOptions.Builder.withDefaults());
		if (!results.isEmpty()) {
			return results;
		}
		return null;
	}

	/**
	 * Récupère la période pour une entité Étude.
	 * 
	 * @param etude
	 * @return
	 */
	public static String getPeriodeEtude(Entity etude) {
		return (String) etude.getProperty("periode");
	}
	
	/**
	 * Méthode qui retourne l'id d'une étude.
	 * @param etude : entitée concernée
	 * @return : un long correpondant à l'id.
	 */
	public static long getIdEtude (Entity etude){
		System.out.println("get id : " + etude.getKey().getId());
		System.out.println("key généré : " + KeyFactory.createKey(nomEntity, etude.getKey().getId()));
		System.out.println("entitée trouvé : " + Util.findEntity(KeyFactory.createKey(nomEntity, etude.getKey().getId())));
		return etude.getKey().getId();
	}
	
	/**
	 * Méthode qui permet de supprimer une étude, ainsi que l'ecole et la
	 * spécialité concernée.
	 * @param id : identificateur de l'entitée
	 */
	public static String deleteEtude(long id){
		Key key = KeyFactory.createKey(nomEntity, id);
		Entity etude = Util.findEntity(key);
		System.out.println("etude :" + etude + " key : " + key);
		if (key != null && etude != null) {
			Ecole.deleteEcole(Ecole.getEcole(etude));
			Util.deleteEntity(key);
			return ("Etude supprimée.");
		} else
			return ("Etude introuvable.");
	}

	/**
	 * Méthode qui permet de supprimer une étude, ainsi que l'ecole et la
	 * spécialité concernée.
	 * @param etude : entitée concernée
	 */
	public static String deleteEtude(Entity etude) {
		Key key = etude.getKey();
		
		if (key != null) {
			Specialite.deleteSpecialite(Specialite.getSpecialite(Ecole.getEcole(etude)));
			Ecole.deleteEcole(Ecole.getEcole(etude));
			Util.deleteEntity(key);
			return ("Etude supprimée.");
		} else
			return ("Etude introuvable.");
		
	}
	
	/**
	 * Parcours de toutes les expériences entre les deux utilisateurs
	 * pour retourner le score de l'expérience la plus intéressante
	 */
	public static double getScoreEtude(String emailUser1, String emailUser2){
		double score=0, scoreMax=0;
		Iterable<Entity> exps1 = Etude.getEtudeForUser(emailUser1);
		Iterable<Entity> exps2 = Etude.getEtudeForUser(emailUser2);
		if(exps1==null || exps2==null) return 0;
		for(Entity e1 : exps1){
			for(Entity e2 : exps2){
				if(Ecole.getEcole(e1)!=null && Ecole.getEcole(e2)!=null) {
					Entity s1 = Specialite.getSpecialite(Ecole.getEcole(e1));
					Entity s2 = Specialite.getSpecialite(Ecole.getEcole(e2));
				if(Ecole.getEcole(e1).getProperty("nom").toString().equals(Ecole.getEcole(e2).getProperty("nom").toString())){
					score = 0.3;
					String[] p1 = e1.getProperty("periode").toString().split("-");
					String[] p2 = e2.getProperty("periode").toString().split("-");
					
					
					if(p1[1].equals("en cours")){
						if(p2[1].equals("en cours")) score = 0.8;
						else 
							if(Integer.parseInt(p1[0]) > Integer.parseInt(p2[1]) ) score = 0.8;
					} else {
						if(p2[1].equals("en cours")) {
							if(Integer.parseInt(p1[1]) < Integer.parseInt(p2[0]) ) score = 0.8;
						}
						else 
							if(Integer.parseInt(p1[1]) < Integer.parseInt(p2[0]) || Integer.parseInt(p1[0]) > Integer.parseInt(p2[1]) ) score = 0.8;
					}
					if (s1.getProperty("nom").equals(s2.getProperty("nom")))
						if (score == 0.8)
							score = 1;
						else
							score = 0.7;
				} else if (s1.getProperty("nom").equals(s2.getProperty("nom")))
					score = 0.1;
				}
				// fin de l'affectation du score, on veut le maximum
				if (score > scoreMax)
					scoreMax = score;
			}
		}
		return scoreMax;
	}

	private static Iterable<Entity> getEtudeForUser(String emailUser1) {
		return Etude.getEtudesForProfil(emailUser1); 
	}

}


